

package com.hazelcast.internal.server.tcp;

import com.hazelcast.internal.networking.Channel;
import com.hazelcast.internal.networking.ChannelInitializer;
import com.hazelcast.internal.networking.ChannelOptions;
import com.hazelcast.internal.server.ServerContext;
import com.hazelcast.spi.properties.HazelcastProperties;

import static com.hazelcast.internal.networking.ChannelOption.*;
import static com.hazelcast.internal.server.ServerContext.KILO_BYTE;
import static com.hazelcast.spi.properties.ClusterProperty.*;

/**
 * A {@link ChannelInitializer} that runs on a member and used for unencrypted
 * channels. It will deal with the exchange of protocols and based on that it
 * will set up the appropriate handlers in the pipeline.
 */
public class UnifiedChannelInitializer implements ChannelInitializer {

    private final ServerContext serverContext;
    private final HazelcastProperties props;

    public UnifiedChannelInitializer(ServerContext serverContext) {
        this.props = serverContext.properties();
        this.serverContext = serverContext;
    }

    @Override
    public void initChannel(Channel channel) {
        ChannelOptions config = channel.options();
        config.setOption(DIRECT_BUF, props.getBoolean(SOCKET_BUFFER_DIRECT)).setOption(TCP_NODELAY, props.getBoolean(SOCKET_NO_DELAY)).setOption(SO_KEEPALIVE, props.getBoolean(SOCKET_KEEP_ALIVE)).setOption(SO_SNDBUF, props.getInteger(SOCKET_SEND_BUFFER_SIZE) * KILO_BYTE).setOption(SO_RCVBUF, props.getInteger(SOCKET_RECEIVE_BUFFER_SIZE) * KILO_BYTE).setOption(SO_LINGER, props.getSeconds(SOCKET_LINGER_SECONDS)).setOption(TCP_KEEPIDLE, props.getInteger(SOCKET_KEEP_IDLE)).setOption(TCP_KEEPCOUNT, props.getInteger(SOCKET_KEEP_COUNT)).setOption(TCP_KEEPINTERVAL, props.getInteger(SOCKET_KEEP_INTERVAL));

        UnifiedProtocolEncoder encoder = new UnifiedProtocolEncoder(serverContext);
        UnifiedProtocolDecoder decoder = new UnifiedProtocolDecoder(serverContext, encoder);

        channel.outboundPipeline().addLast(encoder);
        channel.inboundPipeline().addLast(decoder);
    }
}
